package com.excesys.exsecs.linkage.service.impl;

import cn.hutool.core.util.ObjectUtil;
import cn.hutool.json.JSONArray;
import cn.hutool.json.JSONObject;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.excesys.exsecs.access.constant.RedisConstant;
import com.excesys.exsecs.access.entity.AccessDeviceInfo;
import com.excesys.exsecs.access.entity.AccessThingModel;
import com.excesys.exsecs.access.service.AccessDeviceInfoService;
import com.excesys.exsecs.access.service.AccessThingModelService;
import com.excesys.exsecs.access.vo.ThingInvokeVO;
import com.excesys.exsecs.admin.api.entity.SysDict;
import com.excesys.exsecs.admin.api.entity.SysDictItem;
import com.excesys.exsecs.admin.api.vo.UserVO;
import com.excesys.exsecs.admin.service.SysDictItemService;
import com.excesys.exsecs.admin.service.SysDictService;
import com.excesys.exsecs.admin.service.SysUserService;
import com.excesys.exsecs.alarm.entity.AlarmRecord;
import com.excesys.exsecs.alarm.entity.AlarmTypeConf;
import com.excesys.exsecs.alarm.service.AlarmRecordService;
import com.excesys.exsecs.alarm.service.AlarmTypeConfService;
import com.excesys.exsecs.linkage.alarm.TencentEnterpriseEmailSender;
import com.excesys.exsecs.linkage.entity.*;
import com.excesys.exsecs.linkage.mapper.SceneExecuteActionMapper;
import com.excesys.exsecs.linkage.mapper.SceneLinkageMapper;
import com.excesys.exsecs.linkage.mapper.SceneTriggerMapper;
import com.excesys.exsecs.linkage.service.SceneLinkageLogService;
import com.excesys.exsecs.linkage.service.SceneLinkageService;
import com.excesys.exsecs.linkage.service.SceneTriggerService;
import com.excesys.exsecs.linkage.vo.ConditionVo;
import com.excesys.exsecs.linkage.vo.SceneLinkageVO;
import lombok.RequiredArgsConstructor;
import lombok.SneakyThrows;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;

import java.text.SimpleDateFormat;
import java.time.*;
import java.time.format.DateTimeFormatter;
import java.util.*;

/**
 * 场景触发器
 *
 * @author zhangtailong
 * @date 2024-05-20 16:42:45
 */
@Service
@Slf4j
@RequiredArgsConstructor
public class SceneTriggerServiceImpl implements SceneTriggerService {
	@Autowired
	private SceneTriggerMapper sceneTriggerMapper;

	@Autowired
	private SceneLinkageMapper sceneLinkageMapper;

	@Autowired
	private SceneLinkageService sceneLinkageService;
	@Autowired
	private StringRedisTemplate redisTemplate;

	@Autowired
	private AccessDeviceInfoService accessDeviceInfoService;
	@Autowired
	private SceneExecuteActionMapper sceneExecuteActionMapper;

	@Autowired
	private AccessThingModelService accessThingModelService;

	@Autowired
	private AlarmTypeConfService alarmTypeConfService;
	@Autowired
	private SysDictItemService sysDictItemService;
	@Autowired
	private AlarmRecordService alarmRecordService;
	@Autowired
	private SceneLinkageLogService sceneLinkageLogService;

	@Autowired
	private TencentEnterpriseEmailSender sender;

	@Autowired
	private SysUserService userService;

	@SneakyThrows
	@Override
	public void check(String unitNo, String timeStamp) {
		boolean sign = false;
		boolean sign1 = false;
		boolean timeFlag = false;
		Boolean conditionFlag = false;
		boolean flag = false;
		// 获取当前日期
		LocalDate today = LocalDate.now();
		// 获取星期几
		String dayOfWeek = today.getDayOfWeek().getValue() + "";
		SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
		DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
		// 格式化日期时间
		String formattedDate = sdf.format(new Date());
		//获取当前时分秒用作下面判断是否在触发器时间内
		LocalDateTime dateTime = LocalDateTime.parse(formattedDate, formatter);
		LocalTime time = dateTime.toLocalTime();
		//为空跳过
		if (ObjectUtil.isNotEmpty(sceneTriggerMapper.getInfoByUnitNo(unitNo))) {
			if (sceneTriggerMapper.getInfoByUnitNo(unitNo).size() < 0) {
				return;
			}
		} else {
			return;
		}
		//获取当前设备场景
		List<SceneTrigger> sceneTriggerList = sceneTriggerMapper.getInfoByUnitNo(unitNo);
		for (SceneTrigger sceneTrigger : sceneTriggerList) {
			List<SceneLinkage> sceneLinkageList = sceneLinkageMapper.getSceneLinkageListById(sceneTrigger.getLinkageId());
			for (SceneLinkage sceneLinkage : sceneLinkageList) {
				List<SceneTrigger> triggers = new ArrayList<>();
				SceneLinkageVO sceneLinkageVO = sceneLinkageService.getByLinkageId(sceneLinkage.getLinkageId());
				List<SceneTrigger> triggerList = sceneLinkageVO.getSceneTriggerList();
				List<SceneExecuteAction> executeActionList = sceneLinkageVO.getSceneExecuteActionList();
				List<SceneExecuteConditions> sceneExecuteConditionsList = sceneLinkageVO.getSceneExecuteConditionsList();
				if (triggerList.size() == 0 && sceneExecuteConditionsList.size() == 0) {
					Boolean status = true;
					String Linked = "";
					for (SceneExecuteAction sceneExecuteAction : executeActionList) {
						Linked = sceneExecuteAction.getLinkageId();
						ThingInvokeVO thingInvokeVO = new ThingInvokeVO();
						thingInvokeVO.setService(sceneExecuteAction.getIdentifier());
						thingInvokeVO.setTimestamp(System.currentTimeMillis());
						//执行动作模式 （1设备输出  2关联告警 3消息发送）
						if (sceneExecuteAction.getTriggerMode() == 1) {
							JSONObject jsonObject = new JSONObject();
							for (SceneExecuteActionModel model : sceneExecuteAction.getSceneExecuteActionModelList()) {
								String[] uniiNos = sceneExecuteAction.getUnitNo().split(",");
								for (String unitNO : uniiNos) {
									thingInvokeVO.setUnitNo(unitNO);
									// 如果设备离线，则直接返回离线信息
									AccessDeviceInfo device = accessDeviceInfoService.getOne(Wrappers.<AccessDeviceInfo>lambdaQuery().eq(AccessDeviceInfo::getUnitNo, unitNO));
									if (device.getOnlineStatus() != 0) {
										if ("int32".equals(model.getType())) {
											jsonObject.put(model.getCircuitId(), Integer.valueOf(model.getValue()));
										} else if ("float".equals(model.getType())) {
											jsonObject.put(model.getCircuitId(), Float.valueOf(model.getValue()));
										} else if ("bool".equals(model.getType())) {
											if ("1".equals(model.getValue())) {
												jsonObject.put(model.getCircuitId(), Boolean.TRUE);
											} else {
												jsonObject.put(model.getCircuitId(), Boolean.FALSE);
											}
										} else if ("enum".equals(model.getType())) {
											jsonObject.put(model.getCircuitId(), Integer.valueOf(model.getValue()));
										} else if ("text".equals(model.getType())) {
											jsonObject.put(model.getCircuitId(), String.valueOf(model.getValue()));
										}
									}
								}
							}
							thingInvokeVO.setArgs(jsonObject);
							if (ObjectUtil.isNotEmpty(sceneExecuteAction.getDelayTime())) {
								Thread.sleep(Integer.valueOf(sceneExecuteAction.getDelayTime()) * 1000);
							}
							ThingInvokeVO thingInvokeVO1 = accessDeviceInfoService.invoke(thingInvokeVO);
							System.out.println("thingInvokeVO1:" + thingInvokeVO1);
						} else if (sceneExecuteAction.getTriggerMode() == 2) {
							//根据告警类型走
							AlarmTypeConf alarmTypeConf = alarmTypeConfService.getTypeByCode(sceneExecuteAction.getAlarmId());
							SysDictItem sysDictItem = sysDictItemService.getById(sceneExecuteAction.getAlarmInfo());
							AlarmRecord alarmRecord = new AlarmRecord();
							alarmRecord.setAlarmContent(sysDictItem.getLabel());
							alarmRecord.setUnitNo(sceneTrigger.getUnitNo());
							alarmRecord.setAlarmTypeCode(alarmTypeConf.getTypeCode());
							alarmRecord.setAlarmLevel(Integer.valueOf(alarmTypeConf.getLevel()));
							alarmRecord.setSender(alarmTypeConf.getSender());
							//alarmRecord.setConfigType(sceneTrigger.getConfigType());
							//alarmRecord.setHappenTime(sceneTrigger.getTimeStamp());
							//alarmRecord.setUnit(sceneTrigger.getUnit());
							alarmRecord.setCreateBy("system");
							alarmRecord.setUpdateBy("system");
//							if (sceneTrigger.getConfigType() != 3 || sceneTrigger.getConfigType() != 6) {
//									alarmRecord.setFixedValue(sceneTrigger.getFixedValue());
//									alarmRecord.setAlarmValue(sceneTrigger.getVal().get("nowValue") + "");
//								} else {
//									alarmRecord.setLowerValue(sceneTrigger.getLowerValue());
//									alarmRecord.setUpperValue(sceneTrigger.getUpperValue());
//							}
							status = alarmRecordService.saveRecord(alarmRecord);
						} else if (sceneExecuteAction.getTriggerMode() == 3) {

						}
					}
					SceneLinkageLog sceneLinkageLog = new SceneLinkageLog();
					sceneLinkageLog.setLinkageId(Linked);
					sceneLinkageLog.setSceneName(sceneLinkageVO.getSceneName());
					sceneLinkageLog.setHappenTime(LocalDateTime.now());
					sceneLinkageLog.setInfo("设备触发");
					if (!status) {
						sceneLinkageLog.setStatus(0);
						sceneLinkageLog.setRemarks("执行动作失败");
					} else {
						sceneLinkageLog.setStatus(1);
						sceneLinkageLog.setRemarks("执行动作成功");
					}
					log.info("设备触发打印日志打印日志条件：sceneLinkageLog" + sceneLinkageLog);
					sceneLinkageLogService.save(sceneLinkageLog);
					break;
				}
				if (triggerList.size() > 0) {
					for (SceneTrigger tirgger : triggerList) {
						tirgger.setTimeStamp(LocalDateTime.ofInstant(Instant.ofEpochMilli(Long.parseLong(timeStamp)), ZoneId.systemDefault()));
						//触发器模式 （1设备  2 定时）
						if (tirgger.getTriggerMode() == 1) {
							if (ObjectUtil.isNotEmpty(tirgger.getUnitNo())) {
								String[] unitNos = tirgger.getUnitNo().split(",");
								for (String unitNo1 : unitNos) {
									Object objData = redisTemplate.opsForHash().get(RedisConstant.REPORT_LIST_KEY, unitNo1);
									JSONObject jsonObject = new JSONObject(objData);
									if ("online".equals(tirgger.getChannelNo())) {
										String online = jsonObject.get("online") + "";
										if ("online".equals(tirgger.getChannelNo())) {
											if ("1".equals(online)) {
												sign = true;
												break;
											}
										} else if ("offonline".equals(tirgger.getChannelNo())) {
											if ("0".equals(online)) {
												sign = true;
												break;
											}
										}

									}
									JSONArray jsonArray = getJson(unitNo1);
									if (ObjectUtil.isNotEmpty(jsonArray)) {
										for (int i = 0; i < jsonArray.size(); i++) {
											JSONObject json1 = new JSONObject(jsonArray.get(i));
											if (json1.get("identifier").equals(tirgger.getChannelNo())) {
												JSONObject json2 = new JSONObject(json1.get("dataType"));
												if (ObjectUtil.isNotEmpty(json2.get("type"))) {
													if (ObjectUtil.isNotEmpty(json2.get("type"))) {
														if (ObjectUtil.isNotEmpty(objData)) {
															Map map = (Map) jsonObject.get("data");
															JSONObject jso = new JSONObject();
															jso.set("nowValue", map.get(tirgger.getChannelNo()) + "");
															if ("int32".equals(json2.get("type"))) {
																Integer nowValue = Integer.valueOf(map.get(tirgger.getChannelNo()) + "");
																//0-> 1-< 2-= 3-范围值
																if (tirgger.getConfigType() != 3 || tirgger.getConfigType() != 6) {
																	Integer fixedValue = Integer.valueOf(tirgger.getFixedValue() + "");
																	if (tirgger.getConfigType() == 0) {
																		if (nowValue.compareTo(fixedValue) > 0) {
																			sign = true;
																			tirgger.setUnitNo(unitNo1);
																			tirgger.setVal(jso);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 1) {
																		if (nowValue.compareTo(fixedValue) < 0) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 2) {
																		if (nowValue.compareTo(fixedValue) == 0) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 4) {
																		if (fixedValue >= nowValue) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 5) {
																		if (nowValue <= fixedValue) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	}
																} else {
																	Integer leftValue = Integer.valueOf(tirgger.getLowerValue());
																	Integer rightValue = Integer.valueOf(tirgger.getUpperValue());
																	if (tirgger.getConfigType() == 3) {
																		if (leftValue.compareTo(nowValue) < 0 && rightValue.compareTo(nowValue) > 0) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 6) {
																		if (nowValue < leftValue && nowValue > rightValue) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	}
																}
															} else if ("float".equals(json2.get("type"))) {
																Float nowValue = Float.valueOf(map.get(tirgger.getChannelNo()) + "");
																//0-> 1-< 2-= 3-范围值
																if (tirgger.getConfigType() != 3) {
																	Float fixedValue = Float.valueOf(tirgger.getFixedValue() + "");
																	if (tirgger.getConfigType() == 0) {
																		if (nowValue.compareTo(fixedValue) > 0) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 1) {
																		if (nowValue.compareTo(fixedValue) < 0) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 2) {
																		if (nowValue.compareTo(fixedValue) == 0) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 4) {
																		if (fixedValue >= nowValue) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 5) {
																		if (nowValue <= fixedValue) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	}
																} else {
																	Float leftValue = Float.valueOf(tirgger.getLowerValue());
																	Float rightValue = Float.valueOf(tirgger.getUpperValue());
																	if (tirgger.getConfigType() == 3) {
																		if (leftValue.compareTo(nowValue) < 0 && rightValue.compareTo(nowValue) > 0) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	} else if (tirgger.getConfigType() == 6) {
																		if (nowValue < leftValue && nowValue > rightValue) {
																			sign = true;
																			tirgger.setVal(jso);
																			tirgger.setUnitNo(unitNo1);
																			triggers.add(tirgger);
																			break;
																		}
																	}
																}
															}
														} else {
															break;
														}
													} else {
														break;
													}
												}
											}
											break;
										}

									}
									break;
								}
							}

						} else if (tirgger.getTriggerMode() == 2) {
							List<SceneTriggerTime> sceneTriggerTimes = tirgger.getSpecialDateList();
							//判断是否在设置的星期内
							boolean week = tirgger.getWeek().contains(dayOfWeek);
							boolean value = sceneTriggerTimes.stream().anyMatch(sceneTriggerTime -> today.equals(sceneTriggerTime.getSpecialDate()));
							if (value || week) {
								LocalTime startTime = LocalTime.parse(tirgger.getSetTime());
								timeFlag = !time.isBefore(startTime);
							}
						}
						//设备触发器或时间触发器满足一个跳出循环执行下一步 执行条件
						if (sign || timeFlag) {
							int j = 0;
							JSONObject object = new JSONObject();
							//判断有无重复触发次数&触发时间间隔
							if (ObjectUtil.isNotEmpty(tirgger.getTriggerNumber())) {
								if (ObjectUtil.isNotEmpty(tirgger.getIntervalTime())) {
									Object objData = redisTemplate.opsForHash().get("linked_list", tirgger.getLinkageId());
									if (ObjectUtil.isNotEmpty(objData)) {
										JSONObject jsonObject = new JSONObject(objData);
										j = Integer.valueOf(jsonObject.get("num") + "");
									}
									if (j < tirgger.getTriggerNumber() || j == 0) {
										object.set("num", j + 1);
										object.set("time", LocalDateTime.now());
										redisTemplate.opsForHash().put("linked_list", tirgger.getLinkageId(), object + "");
									} else {
										if (ObjectUtil.isNotEmpty(tirgger.getTriggerConfig())) {
											if (tirgger.getTriggerConfig() == 0) {
												sign1 = true;
											} else {
												if (ObjectUtil.isNotEmpty(tirgger.getSetTime())) {
													Thread.sleep(Integer.valueOf(tirgger.getSetTime()) * 1000);
												}
											}
										}
										break;
									}
								}
							} else {
								sign1 = true;
							}
						} else {
							SceneLinkageLog sceneLinkageLog = new SceneLinkageLog();
							sceneLinkageLog.setLinkageId(sceneLinkageVO.getLinkageId());
							sceneLinkageLog.setSceneName(sceneLinkageVO.getSceneName());
							sceneLinkageLog.setStatus(0);
							sceneLinkageLog.setHappenTime(LocalDateTime.now());
							sceneLinkageLog.setInfo("设备触发");
							sceneLinkageLog.setRemarks("触发器校验失败");
							sceneLinkageLogService.save(sceneLinkageLog);
						}
					}
				}

				//当触发器为多个是走&或者或
				boolean status = false;
				List<SceneExecuteConditions> secList = new ArrayList<>();
				if (sceneExecuteConditionsList.size() > 0) {
					for (SceneExecuteConditions sceneExecuteCondition : sceneExecuteConditionsList) {
						sceneExecuteCondition.setTimeStamp(LocalDateTime.ofInstant(Instant.ofEpochMilli(Long.parseLong(timeStamp)), ZoneId.systemDefault()));
						//执行条件（ 0: 全部条件  1: 任意一个条件）
						if (sceneExecuteCondition.getConditions() == 1) {
							//判断是设备还是时间  1-设备 2-时间
							if (sceneExecuteCondition.getTriggerMode() == 1) {
								if (ObjectUtil.isNotEmpty(sceneExecuteCondition.getUnitNo())) {
									String[] uniiNos = sceneExecuteCondition.getUnitNo().split(",");
									for (String unitNo2 : uniiNos) {
										SceneExecuteConditions sceneExecuteCondition1 = new SceneExecuteConditions();
										BeanUtils.copyProperties(sceneExecuteCondition, sceneExecuteCondition1);
										sceneExecuteCondition1.setUnitNo(unitNo2);
										Object objData = redisTemplate.opsForHash().get(RedisConstant.REPORT_LIST_KEY, unitNo2);
										if (ObjectUtil.isNotEmpty(objData)) {
											JSONObject jsonObject = new JSONObject(objData);
											Map map = (Map) jsonObject.get("data");
											JSONObject jso = new JSONObject();
											jso.set("nowValue", map.get(sceneExecuteCondition.getChannelNo()) + "");
											if ("online".equals(sceneExecuteCondition.getChannelNo())) {
												String online = jsonObject.get("online") + "";
												if (online.equals(sceneExecuteCondition.getFixedValue())) {
													conditionFlag = true;
													break;
												}
											}
											JSONArray jsonArray = getJson(unitNo2);
											if (ObjectUtil.isNotEmpty(jsonArray)) {
												for (int i = 0; i < jsonArray.size(); i++) {
													JSONObject json1 = new JSONObject(jsonArray.get(i));
													if (json1.get("identifier").equals(sceneExecuteCondition.getChannelNo())) {
														JSONObject json2 = new JSONObject(json1.get("dataType"));
														if (ObjectUtil.isNotEmpty(json2.get("type"))) {
															if (ObjectUtil.isNotEmpty(json2.get("type"))) {
																if (ObjectUtil.isNotEmpty(objData)) {
																	if (getBoolean(json2.get("type"), sceneExecuteCondition, map)) {
																		conditionFlag = true;
																		if (sceneExecuteCondition.getConfigType() != 3 || sceneExecuteCondition.getConfigType() != 6) {
																			sceneExecuteCondition1.setVal(jso);
																		}
																		secList.add(sceneExecuteCondition1);
																		execute(triggers, secList, sceneLinkageVO);
																		status = true;
																		break;
																	}
																} else {
																	continue;
																}
															} else {
																continue;
															}
														}
													}
												}

											}
										}
										if (status) {
											break;
										}
									}
								}
							} else if (sceneExecuteCondition.getTriggerMode() == 2) {
								List<SceneExecuteConditions> secs = new ArrayList<>();
								if ("1".equals(sceneExecuteCondition.getTimeScope())) {
									LocalDateTime start1Time = LocalDateTime.parse(sceneExecuteCondition.getStartTime() + "", formatter);
									LocalDateTime end1Time = LocalDateTime.parse(sceneExecuteCondition.getEndTime() + "", formatter);
									// 获取当前时间
									LocalDateTime now = LocalDateTime.now();
									// 判断当前时间是否在时间范围内
									if (!now.isBefore(start1Time) && !now.isAfter(end1Time)) {
										execute(triggers, secs, sceneLinkageVO);
									}
								} else {
									if(sign1){
										execute(triggers, secs, sceneLinkageVO);
									}
								}
							}
						} else if (sceneExecuteCondition.getConditions() == 0) {
							List<Boolean> booleanList = new ArrayList<>();
							//判断是设备还是时间  1-设备 2-时间
							if (sceneExecuteCondition.getTriggerMode() == 1) {
								String[] uniiNos = sceneExecuteCondition.getUnitNo().split(",");
								for (String unitNo3 : uniiNos) {
									SceneExecuteConditions sceneExecuteCondition1 = new SceneExecuteConditions();
									BeanUtils.copyProperties(sceneExecuteCondition, sceneExecuteCondition1);
									sceneExecuteCondition1.setUnitNo(unitNo3);
									Object objData = redisTemplate.opsForHash().get(RedisConstant.REPORT_LIST_KEY, unitNo3);
									if (ObjectUtil.isNotEmpty(objData)) {
										JSONObject jsonObject = new JSONObject(objData);
										Map map = (Map) jsonObject.get("data");
										JSONObject jso = new JSONObject();
										jso.set("nowValue", map.get(sceneExecuteCondition.getChannelNo()) + "");
										JSONArray jsonArray = getJson(unitNo3);
										if ("online".equals(sceneExecuteCondition.getChannelNo())) {
											String online = jsonObject.get("online") + "";
											if (online.equals(sceneExecuteCondition.getFixedValue())) {
												booleanList.add(true);
											} else {
												booleanList.add(false);
											}
										}
										if (ObjectUtil.isNotEmpty(jsonArray)) {
											for (int i = 0; i < jsonArray.size(); i++) {
												JSONObject json1 = new JSONObject(jsonArray.get(i));
												if (json1.get("identifier").equals(sceneExecuteCondition.getChannelNo())) {
													JSONObject json2 = new JSONObject(json1.get("dataType"));
													if (ObjectUtil.isNotEmpty(json2.get("type"))) {
														if (ObjectUtil.isNotEmpty(json2.get("type"))) {
															if (ObjectUtil.isNotEmpty(objData)) {
																if (getBoolean(json2.get("type"), sceneExecuteCondition, map)) {
																	booleanList.add(true);
																	if (sceneExecuteCondition.getConfigType() != 3 || sceneExecuteCondition.getConfigType() != 6) {
																		sceneExecuteCondition1.setVal(jso);
																	}
																	secList.add(sceneExecuteCondition1);
																	break;
																} else {
																	booleanList.add(false);
																	break;
																}
															}
														}
													}
												}
											}

										}
									}
								}
							} else if (sceneExecuteCondition.getTriggerMode() == 2) {
								if ("1".equals(sceneExecuteCondition.getTimeScope())) {
									LocalDateTime start1Time = LocalDateTime.parse(sceneExecuteCondition.getStartTime() + "", formatter);
									LocalDateTime end1Time = LocalDateTime.parse(sceneExecuteCondition.getEndTime() + "", formatter);
									// 获取当前时间
									LocalDateTime now = LocalDateTime.now();
									// 判断当前时间是否在时间范围内
									if (!now.isBefore(start1Time) && !now.isAfter(end1Time)) {
										timeFlag = true;
									}
								} else {
									timeFlag = true;
								}
							}
							if (0 == sceneExecuteConditionsList.size() - 1) {
								if (!booleanList.contains(false)) {
									conditionFlag = true;
								}
								booleanList.clear();
								if (conditionFlag || timeFlag) {
									execute(triggers, secList, sceneLinkageVO);
								} else {
									SceneLinkageLog sceneLinkageLog = new SceneLinkageLog();
									sceneLinkageLog.setLinkageId(sceneLinkageVO.getLinkageId());
									sceneLinkageLog.setSceneName(sceneLinkageVO.getSceneName());
									sceneLinkageLog.setStatus(0);
									sceneLinkageLog.setHappenTime(LocalDateTime.now());
									sceneLinkageLog.setInfo("设备触发");
									sceneLinkageLog.setRemarks("执行条件校验失败");
									sceneLinkageLogService.save(sceneLinkageLog);
								}
							}

						}
						if (status) {
							break;
						}
					}
				}else{
					execute(triggers, secList, sceneLinkageVO);
				}
			}
		}
		return;
	}

	private void execute(List<SceneTrigger> triggers, List<SceneExecuteConditions> secList, SceneLinkageVO sceneLinkageVO) throws Exception {
		Boolean status = true;
		Boolean status1 = true;
		String Linked = "";
		List<Boolean> booleanList = new ArrayList<>();
		List<String> unitNos = new ArrayList<>();
		String alarmId = "";
		if (triggers.size() > 0) {
			for (SceneTrigger sceneTrigger : triggers) {
				ConditionVo conditionVo = new ConditionVo();
				conditionVo.setLinkageId(sceneTrigger.getLinkageId());
				List<SceneExecuteAction> sceneExecuteActions = sceneExecuteActionMapper.getInfoById(conditionVo);
				for (SceneExecuteAction sceneExecuteAction : sceneExecuteActions) {
					Linked = sceneExecuteAction.getLinkageId();
					ThingInvokeVO thingInvokeVO = new ThingInvokeVO();
					thingInvokeVO.setService(sceneExecuteAction.getIdentifier());
					thingInvokeVO.setTimestamp(System.currentTimeMillis());
					//执行动作模式 （1设备输出  2关联告警 3消息发送）
					if (sceneExecuteAction.getTriggerMode() == 1) {
						JSONObject jsonObject = new JSONObject();
						for (SceneExecuteActionModel model : sceneExecuteAction.getSceneExecuteActionModelList()) {
							String[] uniiNos = sceneExecuteAction.getUnitNo().split(",");
							for (String unitNO : uniiNos) {
								thingInvokeVO.setUnitNo(unitNO);
								// 如果设备离线，则直接返回离线信息
								AccessDeviceInfo device = accessDeviceInfoService.getOne(Wrappers.<AccessDeviceInfo>lambdaQuery().eq(AccessDeviceInfo::getUnitNo, unitNO));
								if (device.getOnlineStatus() != 0) {
									if ("int32".equals(model.getType())) {
										jsonObject.put(model.getCircuitId(), Integer.valueOf(model.getValue()));
									} else if ("float".equals(model.getType())) {
										jsonObject.put(model.getCircuitId(), Float.valueOf(model.getValue()));
									} else if ("bool".equals(model.getType())) {
										if ("1".equals(model.getValue())) {
											jsonObject.put(model.getCircuitId(), Boolean.TRUE);
										} else {
											jsonObject.put(model.getCircuitId(), Boolean.FALSE);
										}
									} else if ("enum".equals(model.getType())) {
										jsonObject.put(model.getCircuitId(), Integer.valueOf(model.getValue()));
									} else if ("text".equals(model.getType())) {
										jsonObject.put(model.getCircuitId(), String.valueOf(model.getValue()));
									}
								}
							}
						}
						thingInvokeVO.setArgs(jsonObject);
						if (ObjectUtil.isNotEmpty(sceneExecuteAction.getDelayTime())) {
							Thread.sleep(Integer.valueOf(sceneExecuteAction.getDelayTime()) * 1000);
						}
						ThingInvokeVO thingInvokeVO1 = accessDeviceInfoService.invoke(thingInvokeVO);
						System.out.println("thingInvokeVO1:" + thingInvokeVO1);
					} else if (sceneExecuteAction.getTriggerMode() == 2) {
						alarmId = sceneExecuteAction.getAlarmId();
						unitNos.add(sceneTrigger.getUnitNo());
						//根据告警类型走
						AlarmTypeConf alarmTypeConf = alarmTypeConfService.getTypeByCode(sceneExecuteAction.getAlarmId());
						SysDictItem sysDictItem = sysDictItemService.getById(sceneExecuteAction.getAlarmInfo());
						AlarmRecord alarmRecord = new AlarmRecord();
						alarmRecord.setAlarmContent(sysDictItem.getLabel());
						alarmRecord.setUnitNo(sceneTrigger.getUnitNo());
						alarmRecord.setAlarmTypeCode(alarmTypeConf.getTypeCode());
						alarmRecord.setAlarmLevel(Integer.valueOf(alarmTypeConf.getLevel()));
						alarmRecord.setSender(alarmTypeConf.getSender());
						alarmRecord.setConfigType(sceneTrigger.getConfigType());
						alarmRecord.setHappenTime(sceneTrigger.getTimeStamp());
						alarmRecord.setUnit(sceneTrigger.getUnit());
						alarmRecord.setCreateBy("system");
						alarmRecord.setUpdateBy("system");
						if (sceneTrigger.getConfigType() != 3 || sceneTrigger.getConfigType() != 6) {
							alarmRecord.setFixedValue(sceneTrigger.getFixedValue());
							alarmRecord.setAlarmValue(sceneTrigger.getVal().get("nowValue") + "");
						} else {
							alarmRecord.setLowerValue(sceneTrigger.getLowerValue());
							alarmRecord.setUpperValue(sceneTrigger.getUpperValue());
						}
						status = alarmRecordService.saveRecord(alarmRecord);
					} else if (sceneExecuteAction.getTriggerMode() == 3) {

					}
				}
			}
		}

		if (secList.size() > 0) {
			for (SceneExecuteConditions sec : secList) {
				ConditionVo conditionVo = new ConditionVo();
				conditionVo.setLinkageId(sec.getLinkageId());
				List<SceneExecuteAction> sceneExecuteActions = sceneExecuteActionMapper.getInfoById(conditionVo);
				//根据执行条件任意一个或全部判断执行下一步
				for (SceneExecuteAction sceneExecuteAction : sceneExecuteActions) {
					Linked = sceneExecuteAction.getLinkageId();
					ThingInvokeVO thingInvokeVO = new ThingInvokeVO();
					thingInvokeVO.setService(sceneExecuteAction.getIdentifier());
					thingInvokeVO.setTimestamp(System.currentTimeMillis());
					//执行动作模式 （1设备输出  2关联告警 3消息发送）
					if (sceneExecuteAction.getTriggerMode() == 1) {
						JSONObject jsonObject = new JSONObject();
						for (SceneExecuteActionModel model : sceneExecuteAction.getSceneExecuteActionModelList()) {
							String[] uniiNos = sceneExecuteAction.getUnitNo().split(",");
							for (String unitNO : uniiNos) {
								thingInvokeVO.setUnitNo(unitNO);
								// 如果设备离线，则直接返回离线信息
								AccessDeviceInfo device = accessDeviceInfoService.getOne(Wrappers.<AccessDeviceInfo>lambdaQuery().eq(AccessDeviceInfo::getUnitNo, unitNO));
								if (device.getOnlineStatus() != 0) {
									if ("int32".equals(model.getType())) {
										jsonObject.put(model.getCircuitId(), Integer.valueOf(model.getValue()));
									} else if ("float".equals(model.getType())) {
										jsonObject.put(model.getCircuitId(), Float.valueOf(model.getValue()));
									} else if ("bool".equals(model.getType())) {
										if ("1".equals(model.getValue())) {
											jsonObject.put(model.getCircuitId(), Boolean.TRUE);
										} else {
											jsonObject.put(model.getCircuitId(), Boolean.FALSE);
										}
									} else if ("enum".equals(model.getType())) {
										jsonObject.put(model.getCircuitId(), Integer.valueOf(model.getValue()));
									} else if ("text".equals(model.getType())) {
										jsonObject.put(model.getCircuitId(), String.valueOf(model.getValue()));
									}
								}
							}
						}
						thingInvokeVO.setArgs(jsonObject);
						if (ObjectUtil.isNotEmpty(sceneExecuteAction.getDelayTime())) {
							Thread.sleep(Integer.valueOf(sceneExecuteAction.getDelayTime()) * 1000);
						}
						ThingInvokeVO thingInvokeVO1 = accessDeviceInfoService.invoke(thingInvokeVO);
						System.out.println("thingInvokeVO1:" + thingInvokeVO1);
					} else if (sceneExecuteAction.getTriggerMode() == 2) {
						alarmId = sceneExecuteAction.getAlarmId();
						unitNos.add(sec.getUnitNo());
						//根据告警类型走
						AlarmTypeConf alarmTypeConf = alarmTypeConfService.getTypeByCode(sceneExecuteAction.getAlarmId());
						SysDictItem sysDictItem = sysDictItemService.getById(sceneExecuteAction.getAlarmInfo());
						AlarmRecord alarmRecord = new AlarmRecord();
						alarmRecord.setAlarmContent(sysDictItem.getLabel());
						alarmRecord.setUnitNo(sec.getUnitNo());
						alarmRecord.setAlarmTypeCode(alarmTypeConf.getTypeCode());
						alarmRecord.setAlarmLevel(Integer.valueOf(alarmTypeConf.getLevel()));
						alarmRecord.setSender(alarmTypeConf.getSender());
						alarmRecord.setConfigType(sec.getConfigType());
						alarmRecord.setHappenTime(sec.getTimeStamp());
						alarmRecord.setUnit(sec.getUnit());
						alarmRecord.setCreateBy("system");
						alarmRecord.setUpdateBy("system");
						if (sec.getConfigType() != 3 || sec.getConfigType() != 6) {
							alarmRecord.setAlarmValue(sec.getVal().get("nowValue") + "");
							alarmRecord.setFixedValue(sec.getFixedValue());
						} else {
							alarmRecord.setLowerValue(sec.getLowerValue());
							alarmRecord.setUpperValue(sec.getUpperValue());
						}
						if (ObjectUtil.isNotEmpty(sceneExecuteAction.getDelayTime())) {
							Thread.sleep(Integer.valueOf(sceneExecuteAction.getDelayTime()) * 1000);
						}
						status1 = alarmRecordService.saveRecord(alarmRecord);
						booleanList.add(status1);
					} else if (sceneExecuteAction.getTriggerMode() == 3) {

					}
				}
			}
		}
		SceneLinkageLog sceneLinkageLog = new SceneLinkageLog();
		sceneLinkageLog.setLinkageId(Linked);
		sceneLinkageLog.setSceneName(sceneLinkageVO.getSceneName());
		sceneLinkageLog.setHappenTime(LocalDateTime.now());
		sceneLinkageLog.setInfo("设备触发");
		if (booleanList.contains(false) || !status) {
			sceneLinkageLog.setStatus(0);
			if (!status) {
				sceneLinkageLog.setRemarks("触发器去执行动作失败");
			}
			if (booleanList.contains(false)) {
				sceneLinkageLog.setRemarks("执行条件去执行动作失败");
			}
			if (!status && booleanList.contains(false)) {
				sceneLinkageLog.setRemarks("触发器和执行条件去执行动作都失败");
			}
		} else {
			sceneLinkageLog.setStatus(1);
			sceneLinkageLog.setRemarks("执行动作成功");
		}
		log.info("设备触发打印日志打印日志条件：sceneLinkageLog" + sceneLinkageLog);
		sceneLinkageLogService.save(sceneLinkageLog);
		//推送告警
		String body = "该设备出现异常，请及时处理（设备触发）!";
		String head = "";
		HashSet<String> set = new HashSet<>(unitNos);
		List<String> deduplicatedList = new ArrayList<>(set);
		for(int i=0;i<deduplicatedList.size();i++){
			AccessDeviceInfo accessDeviceInfo  = accessDeviceInfoService.detail(deduplicatedList.get(i));
			head = head+accessDeviceInfo.getDeviceName()+",";
		}
		if (head.endsWith(",")) {
			head = head.substring(0, head.length() - 1);
		}
		body = head+body;
		AlarmTypeConf alarmTypeConf1 =	alarmTypeConfService.getTypeByCode(alarmId);
		if(alarmTypeConf1.getWay().contains("sms")){
			for(int i=0;i<alarmTypeConf1.getSenderList().length;i++){
				UserVO userVO  = userService.selectUserVoById(Long.valueOf(alarmTypeConf1.getSenderList()[i]));
				if(ObjectUtil.isNotEmpty(userVO.getEmail())){
					sender.sendMsg(userVO.getEmail(),body);
				}
			}
		}
	}

	private JSONArray getJson(String unitNo) {
		AccessDeviceInfo accessDeviceInfo = accessDeviceInfoService.detail(unitNo);
		AccessThingModel accessThingModel = accessThingModelService.getThingModelByProductKey(accessDeviceInfo.getProductKey());
		JSONObject json = accessThingModel.getModel();
		JSONArray jsonArray = (JSONArray) json.get("properties");
		return jsonArray;
	}

	private boolean getBoolean(Object obj, SceneExecuteConditions sceneExecuteCondition, Map map) {
		if ("int32".equals(obj)) {
			Integer nowValue = Integer.valueOf(map.get(sceneExecuteCondition.getChannelNo()) + "");
			//0-> 1-< 2-= 3-范围值
			if (sceneExecuteCondition.getConfigType() != 3 || (sceneExecuteCondition.getConfigType() != 6)) {
				Integer fixedValue = Integer.valueOf(sceneExecuteCondition.getFixedValue() + "");
				if (sceneExecuteCondition.getConfigType() == 0) {
					if (nowValue.compareTo(fixedValue) > 0) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 1) {
					if (nowValue.compareTo(fixedValue) < 0) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 2) {
					if (nowValue.compareTo(fixedValue) == 0) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 4) {
					if (fixedValue >= nowValue) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 5) {
					if (nowValue <= fixedValue) {
						return true;
					}
				}
			} else {
				Integer leftValue = Integer.valueOf(sceneExecuteCondition.getLowerValue());
				Integer rightValue = Integer.valueOf(sceneExecuteCondition.getUpperValue());
				if (sceneExecuteCondition.getConfigType() == 3) {
					if (leftValue.compareTo(nowValue) < 0 && rightValue.compareTo(nowValue) > 0) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 6) {
					if (nowValue < leftValue && nowValue > rightValue) {
						return true;
					}
				}

			}
		} else if ("float".equals(obj)) {
			Float nowValue = Float.valueOf(map.get(sceneExecuteCondition.getChannelNo()) + "");
			//0-> 1-< 2-= 3-范围值
			if (sceneExecuteCondition.getConfigType() != 3) {
				Float fixedValue = Float.valueOf(sceneExecuteCondition.getFixedValue() + "");
				if (sceneExecuteCondition.getConfigType() == 0) {
					if (nowValue.compareTo(fixedValue) > 0) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 1) {
					if (nowValue.compareTo(fixedValue) < 0) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 2) {
					if (nowValue.compareTo(fixedValue) == 0) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 4) {
					if (fixedValue >= nowValue) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 5) {
					if (nowValue <= fixedValue) {
						return true;
					}
				}

			} else {
				Float leftValue = Float.valueOf(sceneExecuteCondition.getLowerValue());
				Float rightValue = Float.valueOf(sceneExecuteCondition.getUpperValue());
				if (sceneExecuteCondition.getConfigType() == 3) {
					if (leftValue < nowValue && rightValue > nowValue) {
						return true;
					}
				} else if (sceneExecuteCondition.getConfigType() == 6) {
					if (nowValue < leftValue && nowValue > rightValue) {
						return true;
					}
				}
			}
		}
		return false;
	}
}